package com.satan.novel.book.manager.mq;

import com.satan.novel.common.constant.AmqpConsts;
import lombok.RequiredArgsConstructor;
import org.springframework.amqp.core.AmqpTemplate;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;
import org.springframework.transaction.support.TransactionSynchronization;
import org.springframework.transaction.support.TransactionSynchronizationManager;

/**
 * @Author: Demon
 * @Date: 2024/2/4 16:06
 * @Description: AMQP 消息管理类
 **/
@Component
@RequiredArgsConstructor
public class AmqpMsgManager {
    // 定义一个AmqpTemplate实例，用于发送和接收AMQP消息
    private final AmqpTemplate amqpTemplate;

    // 使用Spring的@Value注解从配置文件中获取'amqp.enabled'属性的值，若不存在则默认为false
// 该变量决定是否启用AMQP消息发送功能
    @Value("${spring.amqp.enabled:false}")
    private boolean amqpEnabled;

    /**
     * 发送小说信息变更的消息
     * 当amqpEnabled为true时，调用sendAmqpMessage方法发送消息到消息队列
     */
    public void sendBookChangeMsg(Long bookId) {
        if (amqpEnabled) {
            sendAmqpMessage(amqpTemplate, AmqpConsts.BookChangeMq.EXCHANGE_NAME, null, bookId);
        }
    }

    // 私有辅助方法，用于发送AMQP消息
// 根据当前事务状态选择立即发送或在事务提交后发送
    private void sendAmqpMessage(AmqpTemplate amqpTemplate, String exchange, String routingKey, Object message) {
        // 检查当前线程是否处于实际活动的事务中
        if (TransactionSynchronizationManager.isActualTransactionActive()) {
            // 如果在事务中，则注册一个事务同步处理器，在事务提交后发送消息
            TransactionSynchronizationManager.registerSynchronization(
                    new TransactionSynchronization() {
                        @Override
                        public void afterCommit() {
                            // 在事务成功提交后，通过AmqpTemplate发送消息至指定交换机和路由键
                            amqpTemplate.convertAndSend(exchange, routingKey, message);
                        }
                    });
            return;
        }

        // 若当前不在事务中，直接使用AmqpTemplate发送消息
        amqpTemplate.convertAndSend(exchange, routingKey, message);
    }

}
